﻿using System;
using System.Linq;
using System.Activities;
using System.Activities.Statements;
using System.Threading;
using SharedInterfaces;
using WorkPersistanceStores.XML;
using System.Runtime.DurableInstancing;
using System.Activities.DurableInstancing;

namespace PickDemo
{

    class Program
    {
        static void Main(string[] args)
        {
            WorkflowApplication app = new WorkflowApplication(new ExpenseClaims());
            XmlWorkflowInstanceStore xml = SetupXmlpersistenceStore(app.Id);
            app.InstanceStore = xml;
            ResumeWorkflowService resume = new ResumeWorkflowService(app);
            PromptService.FormsPromptService promptService = new PromptService.FormsPromptService(resume);

            app.Extensions.Add(promptService);

            ManualResetEvent finished = new ManualResetEvent(false);
            Guid guid = app.Id;

            app.PersistableIdle = (e) =>
            {

                return PersistableIdleAction.Unload;

            };


            app.Idle = (idleArgs) =>
            {
                Console.WriteLine("Application has idled...");
                WorkflowApplication a = new WorkflowApplication(new ExpenseClaims());
                XmlWorkflowInstanceStore xml1 = SetupXmlpersistenceStore(guid);
                a.InstanceStore = xml1;
                a.Load(guid);
                //a.ResumeBookmark("ApprovedBookmark", "success");

            };

            app.Completed = (completedArgs) => { finished.Set(); };

            app.Run();

            finished.WaitOne();

            LoadAndCompleteInstance(guid, xml);
        }

        static void LoadAndCompleteInstance(Guid id, InstanceStore instanceStore)
        {

            AutoResetEvent waitHandler = new AutoResetEvent(false);

            Console.WriteLine("Press <enter> to load the persisted workflow");

            Console.ReadLine();

            WorkflowApplication wfApp = new WorkflowApplication(new ExpenseClaims());

            wfApp.InstanceStore = instanceStore;

            wfApp.Completed = (workflowApplicationCompletedEventArgs) =>
            {

                Console.WriteLine("\nWorkflowApplication has Completed in the {0} state.", workflowApplicationCompletedEventArgs.CompletionState);

            };

            wfApp.Unloaded = (workflowApplicationEventArgs) =>
            {

                Console.WriteLine("WorkflowApplication has Unloaded\n");

                waitHandler.Set();

            };

            wfApp.Load(id);

            wfApp.Run();
            waitHandler.WaitOne();

        }


        private static XmlWorkflowInstanceStore SetupXmlpersistenceStore(Guid workflowId)
        {

            XmlWorkflowInstanceStore instanceStore = new XmlWorkflowInstanceStore(workflowId);

            InstanceHandle handle = instanceStore.CreateInstanceHandle();

            InstanceView view = instanceStore.Execute(handle,
                                                    new CreateWorkflowOwnerCommand(),
                                                    TimeSpan.FromSeconds(5));

            handle.Free();

            instanceStore.DefaultInstanceOwner = view.InstanceOwner;

            return instanceStore;

        }

    }



    public class ResumeWorkflowService : IResumeWorkflow
    {
        public ResumeWorkflowService(WorkflowApplication app)
        {
            _app = app;
        }

        public void Resume(string bookmarkName)
        {
            _app.ResumeBookmark(bookmarkName, null);
        }

        private WorkflowApplication _app;
    }
}
